const DB = require('../core/DB')
const {
    Op
} = require('sequelize')
const {
    db_config
} = require('../../bin/config')
const article = require('../models/article')

DB.article.hasMany(DB.tag_article)
DB.article.hasOne(DB.article_info)
DB.tag_article.belongsTo(DB.article)
DB.tag_article.belongsTo(DB.tag)


class ArticleController {
    /* --------------------------------------------------------------------ok 后台检索文章 -------------------------------*/
    async adminSearch(ctx) {
        // 参数
        let {
            key = '', // 关键词
            status,
            tagId = '',
            page = 1,
            size = 10
        } = ctx.request.query


        page = Number(page)
        size = Number(size)


        var rows = [],
            count = 0;

        // 根据标签查询
        if (tagId) {
            let list = await DB.tag_article.findAll({
                where: {
                    tagId
                },
                offset: (page - 1) * size,
                limit: size,
            })

            count = list.length

            if (list.length > 0) {
                for (let item of list) {
                    let id = item.get('articleId')
                    let article = await DB.article.findAll({
                        where: {
                            id,
                            title: {
                                [Op.like]: `%${key}%`
                            },
                            status: {
                                [Op.in]: status ? [status] : [0, 1, 2] // 审核状态
                            }
                        },
                    })
                    rows.push(...article)
                }
            }
        } else {
            // 默认查询
            var {
                count,
                rows
            } = await DB.article.findAndCountAll({
                order: [
                    ['sort', 'DESC'],// 排序
                    ['id', 'DESC'],
                ],
                where: {
                    title: {
                        [Op.like]: `%${key}%`
                    },
                    status: {
                        [Op.in]: status ? [status] : [0, 1, 2] // 审核状态
                    }
                },
                offset: (page - 1) * size,
                limit: size,
            })
        }


        for (let item of rows) {
            let articleId = item.get('id')
            let t_a = await DB.tag_article.findAll({
                where: {
                    articleId
                },
                include: DB.tag
            })

            let arr = []
            for (let v of t_a) {
                arr.push(v.get('tag'))
            }

            item.dataValues.tags = arr
        }

        const data = {
            rows,
            meta: {
                key,
                count, // 条目总数
            }
        }
        global.Response.success(ctx, undefined, data)
    }

    /* --------------------------------------------------------------------ok 获取文章条形图数据 -------------------------------*/
    async getArticleBar(ctx) {
        // 获取当前年份
        const nowYear = global.Moment().format('YYYY')

        const months = [];
        for (let i = 1; i <= 12; i++) {
            months.push({
                month: i,
                count: 0
            })
        }

        const articles = await DB.article.findAll({
            where: {
                createdAt: {
                    [Op.gt]: nowYear // 寻找今年文章
                },
                status: 1
            }
        })

        articles.forEach(item => {
            // 
            let monthIndex = global.Moment(item.createdAt).format('M')
            months[monthIndex - 1].count++;
        })

        global.Response.success(ctx, undefined, months)
    }

    /* -------------------------------------------------------------------- ok 文章点赞和浏览 -------------------------------*/
    async updateArticleInfo(ctx) {
        let {
            like,
            browse,
            articleId
        } = ctx.request.body

        try {
            if (like) {
                await DB.article_info.increment({
                    like: 1
                }, {
                    where: {
                        articleId
                    }
                })
            } else if (browse) {
                await DB.article_info.increment({
                    browse: 1
                }, {
                    where: {
                        articleId
                    }
                })
            }
            global.Response.success(ctx, undefined, DB.article_info)
        } catch (err) {
            global.Response.error(ctx, err)
        }

    }

    /* -------------------------------------------------------------------- ok 获取时间轴 -------------------------------*/
    async getTimeline(ctx) {
        const articles = await DB.article.findAll({
            where: {
                status: 1
            },
            order: [
                ['createdAt', 'DESC']
            ],
        })

        // 声明空数组 存储间隔年份
        let timeTineArr = []

        if (articles.length == 0) {
            global.Response.success(ctx, '暂无文章', timeTineArr)
            return false;
        }

        // 获取首尾巴年份 依次获取各年份
        const endYear = global.Moment(articles[0].createdAt)
        const startYear = global.Moment(articles[articles.length - 1].createdAt)

        while (startYear <= endYear) { // 要确保 startYear 小于 endYear !!
            timeTineArr.push({
                currentYear: startYear.format('YYYY'),
                currentArticles: []
            })
            startYear.add(1, 'years')
        }

        articles.forEach(article => {
            // 对每年份遍历
            timeTineArr.forEach(time => {
                if (global.Moment(article.createdAt).format('YYYY') == time.currentYear) {
                    time.currentArticles.push(article)
                }
            })
        })

        timeTineArr.reverse() // 年份反转，如果前面已倒序 则不用反转

        global.Response.success(ctx, undefined, timeTineArr)
    }


    /* -------------------------------------------------------------------- ok 新增文章 -------------------------------*/
    async createArticle(ctx) {
        // 参数
        let {
            title, // 标题
            md, // 内容
            description = '', // 描述
            tags, // 标签id 默认数组
            img = '', // 图片链接
            status = 1,
            sort = 1,
            seo = '',
        } = ctx.request.body

        // json解析
        tags = JSON.parse(tags)

        // 创建文章
        const article = await DB.article.create({
            title,
            description,
            md,
            img,
            status,
            sort,
            seo,
            createdAt: global.Moment().format('YYYY-MM-DD HH:mm:ss'),
            updatedAt: global.Moment().format('YYYY-MM-DD HH:mm:ss'),
            article_info: {
                like: 0,
                browse: 0
            }
        }, {
            include: DB.article_info
        })

        // 循环标签数组
        for (let i in tags) {
            await DB.tag_article.create({
                tagId: tags[i],
                articleId: article.get('id')
            })
        }

        global.Response.success(ctx, '创建成功', article)
    }

    /* ------------------------------------------------------------------- ok 文章草稿 -------------------------------*/
    async listDraft(ctx) {
        // 参数
        let {
            page = 1, size = 10, key = '' // 关键词
        } = ctx.query

        page = Number(page)
        size = Number(size)

        const {
            count,
            rows
        } = await DB.article.findAndCountAll({
            offset: (page - 1) * size,
            limit: size,
            order: [
                ['sort', 'DESC'],// 排序
                ['id', 'DESC']
            ],
            where: {
                status: 2
            }
        })

        for (let article of rows) {
            let articleId = article.get('id')
            let t_a = await DB.tag_article.findAll({
                where: {
                    articleId
                },
                include: DB.tag
            })

            let arr = []
            for (let v of t_a) {
                arr.push(v.get('tag'))
            }

            article.dataValues.tags = arr
        }

        const data = {
            rows,
            meta: {
                key,
                size, // 每页条目
                count: count, // 条目总数
                page: page, // 当前页数
                total: Math.ceil(count / size), // 总页数
            }
        }
        global.Response.success(ctx, undefined, data)
    }

    /* ------------------------------------------------------------------- ok 后台获取所有文章 -------------------------------*/
    async listAdminArticle(ctx) {
        // 参数
        let {
            page = 1, size = 10, key = '' // 关键词
        } = ctx.query

        page = Number(page)
        size = Number(size)

        const {
            count,
            rows
        } = await DB.article.findAndCountAll({
            offset: (page - 1) * size,
            limit: size,
            order: [
                ['sort', 'DESC'],// 排序
                ['id', 'DESC']
            ],
            where: {
                status: {
                    [Op.ne]: 2 // 排除草稿箱
                }
            }
        })

        for (let article of rows) {
            let articleId = article.get('id')
            let t_a = await DB.tag_article.findAll({
                where: {
                    articleId
                },
                include: DB.tag
            })

            let arr = []
            for (let v of t_a) {
                arr.push(v.get('tag'))
            }

            article.dataValues.tags = arr
        }

        const data = {
            rows,
            meta: {
                key,
                size, // 每页条目
                count: count, // 条目总数
                page: page, // 当前页数
                total: Math.ceil(count / size), // 总页数
            }
        }
        global.Response.success(ctx, undefined, data)
    }

    /* -------------------------------------------------------------------- ok 获取指定文章详情 -------------------------------*/
    async getArticleDetail(ctx) {
        let { id: articleId } = ctx.query
        const article = await DB.article.findByPk(articleId)

        if (!article) {
            global.Response.null(ctx)
            return
        }

        // 加载标签
        let t_a = await DB.tag_article.findAll({
            where: {
                articleId
            },
            include: DB.tag
        })

        let arr = []
        for (let v of t_a) {
            arr.push(v.get('tag'))
        }

        article.dataValues.tags = arr

        global.Response.success(ctx, undefined, article)
    }

    /* -------------------------------------------------------------------- ok 更新文章 -------------------------------*/
    async updateArticle(ctx) {
        let {
            id,
            tags
        } = ctx.request.body
        let params = {
            ...ctx.request.body
        }
        delete params.id

        // 跟新标签信息
        if (tags) {
            delete params.tags

            let articleId = id
            tags = JSON.parse(tags)
            // 先删除原先标签，再添加
            await DB.tag_article.destroy({
                where: {
                    articleId
                }
            })

            // 添加 循环标签数组
            for (let i in tags) {
                await DB.tag_article.create({
                    tagId: tags[i],
                    articleId
                })
            }
        }

        console.log(params)

        // 更新文章信息
        const article = await DB.article.update(params, {
            where: {
                id
            }
        })

        global.Response.success(ctx, '更新成功')

    }

    /* -------------------------------------------------------------------- ok 删除指定文章 -------------------------------*/
    async deleteArticle(ctx) {
        const { id } = ctx.query
        await DB.article.destroy({
            where: {
                id
            }
        }) // 返回值 0 or 1
        await DB.tag_article.destroy({
            where: {
                articleId: id
            }
        })

        // 删除其下评论和回复
        let comments = await DB.comment.findAll({
            where: {
                articleId: id
            }
        })
        if (comments.length > 0) {
            for (let i in comments) {
                await DB.reply.destroy({
                    where: {
                        commentId: comments[i].get('id')
                    }
                })
            }
        }
        await DB.comment.destroy({
            where: {
                articleId: id
            }
        })

        global.Response.success(ctx, '删除成功')
    }


}

module.exports = new ArticleController